﻿#include "FITKXYPlotWindow.h"
#include "ui_FITKXYPlotWindow.h"
#include "FITKXYPlotCurveStyle.h"
#include "FITKXYPlotProperty.h"
#include "FITKXYCurveDrawManager.h"

#include <qwt_plot.h>
#include <qwt_scale_engine.h>
#include <qwt_legend.h>
#include <qwt_plot_canvas.h>
#include <qwt_plot_magnifier.h>
#include <qwt_plot_panner.h>
#include <qwt_plot_curve.h>

#include <QToolBar>

namespace Plot
{
    FITKXYPlotWindow::FITKXYPlotWindow(QWidget* parent/*= nullptr*/)
        :Core::FITKAbstractGraph2DWidget(parent)
    {
        _ui = new Ui::FITKXYPlotWindow;
        _ui->setupUi(this);

        _plotWidget = new QwtPlot;
        _ui->gridLayout->addWidget(_plotWidget);
        _plotProperty = new FITKXYPlotProperty(this);
        _curveDrawManager = new FITKXYCurveDrawManager(this);

    //画布边距留白
        //_plotWidget->canvas()->setContentsMargins(18, 0, 18, 10);

    //滚轮放大缩小
        (void) new QwtPlotMagnifier(_plotWidget->canvas());

    //使用鼠标左键平移 
        (void) new QwtPlotPanner(_plotWidget->canvas());

    //背景色
        _plotWidget->canvas()->setStyleSheet(
            "border: 1px solid Black;"
            "border-radius: 1px;"
            "background-color: rgb(250,250,255,190)"
        );
    //刻度值字体
        QFont font;
        font.setPointSize(13); 
        font.setBold(false);  //是否加粗
        _plotWidget->setAxisFont(QwtPlot::Axis::yLeft, font);
        _plotWidget->setAxisFont(QwtPlot::Axis::xBottom, font);

    //坐标轴底部曲线图例
        QwtLegend*_legend = new QwtLegend(_plotWidget);
        _legend->setDefaultItemMode(QwtLegendData::Mode::Clickable);
        font.setPointSize(12);
        _legend->setFont(font);
        _plotWidget->insertLegend(_legend, QwtPlot::BottomLegend);
        connect(_legend, SIGNAL(clicked(const QVariant&, int)), this, SLOT(legendClicked(const QVariant&, int)));

    //自动更新画布设置
        //const bool doAutoReplot = _plotWidget->autoReplot();
        _plotWidget->setAutoReplot(false);
        //_plotWidget->setAutoReplot(doAutoReplot);
        _plotWidget->replot();

    //添加工具栏
        _renderToolBar = new QToolBar();
        _renderToolBar->setContentsMargins(0, 0, 0, 0);
        _renderToolBar->setIconSize(QSize(40, 40));
        initActions();

    //添加到QwtPlot上的所有图元项将在QwtPlot回收时，将自动析构
        _plotWidget->setAutoDelete(true);
    }

    FITKXYPlotWindow::~FITKXYPlotWindow()
    {
        if (_ui) delete _ui;
        _ui = nullptr;
        if (_curveDrawManager) delete _curveDrawManager;
        _curveDrawManager = nullptr;
        if (_plotProperty) delete _plotProperty;
        _plotProperty = nullptr; 
        if (_renderToolBar) delete _renderToolBar;
        _renderToolBar = nullptr;
    //最后析构Plot
        if (_plotWidget) delete _plotWidget;
        _plotWidget = nullptr;
    }

    QwtPlot* FITKXYPlotWindow::getPlotWidget()
    {
        return _plotWidget;
    }

    QToolBar * FITKXYPlotWindow::getToolBar()
    {
        return _renderToolBar;
    }

    FITKXYPlotProperty * FITKXYPlotWindow::getPlotProperty()
    {
        return _plotProperty;
    }

    FITKXYCurveDrawManager * FITKXYPlotWindow::getCurveManager()
    {
        return _curveDrawManager;
    }

    void FITKXYPlotWindow::replaceBorderPoint(double xmin, double xmax, double ymin, double ymax)
    {
        if (xmin < _Xmin) _Xmin = xmin;
        if (ymin < _Ymin) _Ymin = ymin;
        if (xmax > _Xmax) _Xmax = xmax;
        if (ymax > _Ymax) _Ymax = ymax;
    }

    void FITKXYPlotWindow::updataCanvas()
    {
    //如果Floating这项属性被设置为真，代表该轴变为Log指数轴
        bool yLeft =_plotWidget->axisScaleEngine(QwtPlot::yLeft)->testAttribute(QwtScaleEngine::Floating);
        bool xBottom = _plotWidget->axisScaleEngine(QwtPlot::xBottom)->testAttribute(QwtScaleEngine::Floating);
        if (yLeft) {
            _plotWidget->setAxisScale(QwtPlot::yLeft, _Ymin, _Ymax, 0);
        } else {
            double offset_y = (_Ymax - _Ymin) / 16;
            _plotWidget->setAxisScale(QwtPlot::yLeft, _Ymin - offset_y, _Ymax + offset_y, 0);
        }
        if (xBottom) {
            _plotWidget->setAxisScale(QwtPlot::xBottom, _Xmin, _Xmax, 0);
        } else {
            double offset_x = (_Xmax - _Xmin) / 16;
            _plotWidget->setAxisScale(QwtPlot::xBottom, _Xmin - offset_x, _Xmax + offset_x, 0);
        }  
        _plotWidget->replot();
    }

    void FITKXYPlotWindow::initActions()
    {
        QList<QAction*> actions = {};
        QAction* action = nullptr;

    //复位界面按钮
        action = new QAction();
        action->setObjectName("actionRefreshPlot");
        action->setIcon(QIcon(":FITKIcons/icoR_synchLayers.svg"));
        connect(action, SIGNAL(triggered()), this, SLOT(slotActionRefreshPlotEvent()));
        actions.append(action);
    //改样式按钮
        action = new QAction();
        action->setObjectName("actionStylePlot");
        action->setIcon(QIcon(":FITKIcons/icoR_options.svg"));
        connect(action, SIGNAL(triggered()), this, SLOT(slotActionStyleEvent()));
        actions.append(action);

    //追加action
        _renderToolBar->insertActions(nullptr, actions);
        _renderToolBar->setOrientation(Qt::Vertical);
        _ui->gridLayout_2->addWidget(_renderToolBar, 0, 1, Qt::AlignRight | Qt::AlignTop);
    }

    void FITKXYPlotWindow::legendClicked(const QVariant& va, int index)
    {
        QwtPlotItem* plotItem = _plotWidget->infoToItem(va);
        if (plotItem == nullptr) return;
        auto  curve = dynamic_cast<QwtPlotCurve*>(plotItem);

    //曲线是否可见
        if (curve->isVisible()) 
            curve->setVisible(false);
        else 
            curve->setVisible(true);
        _plotWidget->replot();
    }

    void FITKXYPlotWindow::slotActionRefreshPlotEvent()
    {
        QwtPlotItemList curves = _plotWidget->itemList(QwtPlotItem::Rtti_PlotCurve);
        for (QwtPlotItem* item : curves) {
            item->setVisible(true);
        }
        updataCanvas();
    }

    void FITKXYPlotWindow::slotActionStyleEvent()
    {
        FITKXYPlotCurveStyle dlg(this);
    }
}

